package com.iflytek;

import android.app.Application;
import android.content.Context;
import android.graphics.Bitmap;
import android.util.Log;

import com.iflytek.cloud.ErrorCode;
import com.iflytek.cloud.IdentityListener;
import com.iflytek.cloud.IdentityVerifier;
import com.iflytek.cloud.InitListener;
import com.iflytek.cloud.SpeechConstant;
import com.iflytek.cloud.SpeechUtility;

import java.io.ByteArrayOutputStream;

/**
 * Created by ClearLiang on 2019/2/15
 * <p>
 * Function : 人脸识别工具类
 */
public class SpeechUtil {
    private static SpeechUtil instance;
    //采用身份识别接口进行在线人脸识别
    public IdentityVerifier mIdVerifier;

    private SpeechUtil() {
    }

    public static SpeechUtil getSpeechUtil() {
        if (instance == null) {
            synchronized (SpeechUtil.class) {
                if (instance == null) {
                    instance = new SpeechUtil();
                }
            }
        }
        return instance;
    }

    /**
     * 1.一般在 BaseApplication 初始化
     *
     * @param application
     * @param appId
     */
    public void initSpeech(Application application, String appId) {
        // 参数需要以键值对的形式存储在字符串中传入createUtility方法，以逗号隔开，
        // 如“appid=12345678,usr=iflytekcloud,pwd=123456”
        // https://doc.xfyun.cn/msc_android/%E9%A2%84%E5%A4%87%E5%B7%A5%E4%BD%9C.html
        SpeechUtility.createUtility(application, "appid=" + appId);
    }

    /**
     * 2.初始化引擎，需要activity中传context
     *
     * @param context
     */
    public void initVerifier(Context context) {
        mIdVerifier = IdentityVerifier.createVerifier(context, new InitListener() {
            @Override
            public void onInit(int errorCode) {
                if (ErrorCode.SUCCESS == errorCode) {
                    Log.e("信息", "引擎初始化成功");
                } else {
                    Log.e("信息", "引擎初始化失败,错误码" + errorCode);
                }
            }
        });
    }

    /**
     * 注册人脸识别
     *
     * @param authId
     * @param enrollListener
     * @param imageData
     */
    public void register(String authId, IdentityListener enrollListener, byte[] imageData) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null); // 清空参数
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ifr");
        mIdVerifier.setParameter(SpeechConstant.MFV_SST, "enroll");
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);
        mIdVerifier.startWorking(enrollListener);

        // 子业务执行参数，若无可以传空字符传
        StringBuffer params = new StringBuffer();
        // 向子业务写入数据，人脸数据可以一次写入
        mIdVerifier.writeData("ifr", params.toString(), imageData, 0, imageData.length);
        // 停止写入
        mIdVerifier.stopWrite("ifr");
    }

    public void register(String authId, IdentityListener enrollListener, Bitmap bitmap) {
        ByteArrayOutputStream stream = new ByteArrayOutputStream();
        //可根据流量及网络状况对图片进行压缩
        bitmap.compress(Bitmap.CompressFormat.JPEG, 80, stream);
        register(authId, enrollListener, stream.toByteArray());
    }

    /**
     * 验证人脸识别（1：1验证）
     *
     * @param mAuthid
     * @param mImageData
     * @param mVerifyListener
     */
    public void verify(String mAuthid, byte[] mImageData, IdentityListener mVerifyListener) {
        // 注册或验证声纹或人脸时，须指定以下参数：
        // 业务类型（MFV_SST）
        // 业务场景（MFV_SCENES）
        // 用户 ID（AUTH_ID）
        // 验证模式（MFV_VCM）=> 验证必须有该参数

        // 清空参数
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        // 设置会话场景
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ifr");
        // 设置会话类型
        mIdVerifier.setParameter(SpeechConstant.MFV_SST, "verify");
        // 验证时，可通过 MFV_VCM 指定验证模式为单一（人脸或声纹），还是混合（人脸+声纹）。在混合模式下，需要分别写入图片和音频数据。
        // 验证模式，仅在验证场景下使用
        // sin（单一特征），mix（融合），agi（灵活）
        // 无默认值，在验证场景下必须指定
        mIdVerifier.setParameter(SpeechConstant.MFV_VCM, "sin");
        // 用户id
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, mAuthid);
        // 设置监听器，开始会话
        mIdVerifier.startWorking(mVerifyListener);

        // 子业务执行参数，若无可以传空字符传
        StringBuffer params = new StringBuffer();
        // 向子业务写入数据，人脸数据可以一次写入
        mIdVerifier.writeData("ifr", params.toString(), mImageData, 0, mImageData.length);
        // 停止写入
        mIdVerifier.stopWrite("ifr");
    }

    /**
     * 删除人脸模型
     *
     * @param deleteListener
     */
    public void deleteModel(IdentityListener deleteListener) {
        // 设置模型参数，若无可以传空字符传
        StringBuffer params = new StringBuffer();
        // 执行模型操作
        mIdVerifier.execute("ifr", "delete", params.toString(), deleteListener);
    }

    /**
     * 创建组
     *
     * @param groupName
     * @param authId
     * @param mCreateListener
     */
    public void createGroup(String groupName, String authId, IdentityListener mCreateListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        // 设置会话场景
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ipt");
        // 用户id
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);

        // 设置模型参数，若无可以传空字符传
        StringBuffer params = new StringBuffer();
        params.append("auth_id=" + authId);
        params.append(",scope=group");
        params.append(",group_name=" + groupName);
        // 执行模型操作
        mIdVerifier.execute("ipt", "add", params.toString(), mCreateListener);
    }

    /**
     * 加入组
     *
     * @param groupId
     * @param authId
     * @param mAddListener
     */
    public void joinGroup(String groupId, String authId, IdentityListener mAddListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ipt");
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);

        // 设置模型参数，若无可以传空字符传
        StringBuffer params2 = new StringBuffer();
        params2.append("auth_id=" + authId);
        params2.append(",scope=person");
        params2.append(",group_id=" + groupId);
        // 执行模型操作
        mIdVerifier.execute("ipt", "add", params2.toString(), mAddListener);
    }

    /**
     * 查询指定组中的所有成员
     *
     * @param authId
     * @param groupId
     * @param mQueryListener
     */
    public void queryGroup(String authId, String groupId, IdentityListener mQueryListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ipt");
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);
        // 设置模型参数，若无可以传空字符传
        StringBuffer params2 = new StringBuffer();
        params2.append("scope=group");
        params2.append(",group_id=" + groupId);
        // 执行模型操作
        mIdVerifier.execute("ipt", "query", params2.toString(), mQueryListener);
    }

    /**
     * 查询当前appid 下所有组
     * 此处特别申明：***查询所有组信息能力仅提供用于开发者debug所用，如果用于其他
     * 场景或者处于其他目的，责任由程序开发者自付***
     */
    public void queryGroups(IdentityListener mQueryListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, "wer");
        // 设置模型参数，若无可以传空字符传
        StringBuffer params2 = new StringBuffer();
        params2.append("scope=appid");
        // 执行模型操作
        mIdVerifier.execute("ipt", "query", params2.toString(), mQueryListener);
    }

    /**
     * 删除组内成员
     *
     * @param groupId
     * @param authId
     * @param mDeleteListener
     */
    public void deleteGroupPerson(String groupId, String authId, IdentityListener mDeleteListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ipt");
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);

        // 设置模型参数，若无可以传空字符传
        StringBuffer params2 = new StringBuffer();
        // 删除组中指定auth_id用户
        params2.append("auth_id=" + authId);
        params2.append(",scope=person");
        params2.append(",group_id=" + groupId);
        // 执行模型操作
        mIdVerifier.execute("ipt", "delete", params2.toString(), mDeleteListener);
    }

    /**
     * 删除组
     *
     * @param groupId
     * @param authId
     * @param mDeleteListener
     */
    public void deleteGroup(String groupId, String authId, IdentityListener mDeleteListener) {
        mIdVerifier.setParameter(SpeechConstant.PARAMS, null);
        mIdVerifier.setParameter(SpeechConstant.MFV_SCENES, "ipt");
        mIdVerifier.setParameter(SpeechConstant.AUTH_ID, authId);

        // 设置模型参数，若无可以传空字符传
        StringBuffer params2 = new StringBuffer();
        params2.append("scope=group");
        params2.append(",group_id=" + groupId);
        // 执行模型操作
        mIdVerifier.execute("ipt", "delete", params2.toString(), mDeleteListener);
    }


}
